package com.databaseManager;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

public class DatabaseFunc extends DatabaseManager implements IdatabaseFunc {
    /**
     * 新增病历
     * @param data 参数数组，构造格式为{Rid, Pid, Eid, Utime, treat, seeType, onsetDate, drugHistory, mainComplaint, curMedicalHistory}
     * @see DatabaseFunc#insertRecord(String, String, String, String, String, String, String, String, String, String) 
     * @throws Exception
     */
    @Override
    public void insertRecord(Object[] data) throws Exception {
        //预处理sql
        String mySql = SqlFunc.SQL_INSERT_RECORD;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    /**
     * 新增病历
     * @param Rid 病历编号，长度为15位的字符串，主键，非空
     * @param Pid 病人身份证号，长度为18位的字符串，注意外键约束，非空
     * @param Eid 医生编号，长度为18位的字符串，注意外键约束，非空
     * @param Utime 病历填写日期，格式为yyyy-mm-dd或yyyy.mm.dd，非空
     * @param treat 诊断，不限长度的字符串，非空
     * @param seeType 就诊类型，长度为2，通常用“初诊”或“复诊”，非空
     * @param onsetDate 发病日期，格式为yyyy-mm-dd或yyyy.mm.dd，非空
     * @param drugHistory 药物史，非空
     * @param mainComplaint 主诉，非空
     * @param curMedicalHistory 现病史，非空
     * @throws Exception
     */
    @Override
    public void insertRecord(String Rid, String Pid, String Eid, String Utime, String treat, String seeType, 
                             String onsetDate, String drugHistory, String mainComplaint, String curMedicalHistory) throws Exception {
        insertRecord(new Object[] {Rid, Pid, Eid, Utime, treat, seeType, onsetDate, drugHistory, mainComplaint, curMedicalHistory});
    }

    /**
     * 新增病历
     * @param r 病历实例对象，构造格式详见Record类
     * @see Record#Record(String, String, String, String, String, String, String, String, String, String) 
     * @throws Exception
     */
    @Override
    public void insertRecord(Record r) throws Exception {
        insertRecord(r.getRid(), r.getPid(), r.getEid(), r.getUpadteDate(), r.getTreat(), r.getDiagType(), r.getInfectDate(), r.getDrugHistory(),
                r.getMainComplaint(), r.getCurMedicalHistory());
    }

    /**
     * 更改旧病历
     * @param data 参数数组，构造格式为{Utime, onsetDate, treat, drugHistory, mainComplaint, curMedicalHistory, Rid}
     * @see DatabaseFunc#updateRecord(String, String, String, String, String, String, String)
     * @throws Exception
     */
    @Override
    public void updateRecord(Object[] data) throws Exception {
        //预处理sql
        String mySql = SqlFunc.SQL_UPDATE_RECORD;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.UPDATE, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    /**
     * 更改旧病历
     * @param Utime 病历填写日期，格式为yyyy-mm-dd或yyyy.mm.dd，非空
     * @param onsetDate 发病日期，格式为yyyy-mm-dd或yyyy.mm.dd，非空
     * @param treat 诊断，不限长度的字符串，非空
     * @param drugHistory 药物史，非空
     * @param mainComplaint 主诉，非空
     * @param curMedicalHistory 现病史，非空
     * @throws Exception
     */
    @Override
    public void updateRecord(String Rid, String Utime, String treat, String onsetDate, String drugHistory, String mainComplaint, 
    						 String curMedicalHistory) throws Exception {
    	updateRecord(new Object[] {Utime, onsetDate, treat, drugHistory, mainComplaint, curMedicalHistory, Rid});
    }
    
    /**
     * 更改旧病历 
     * @param r 病历实例对象，构造格式详见Record类
     * @see Record#Record(String, String, String, String, String, String, String, String, String, String) 
     * @throws Exception
     */
    @Override
    public void updateRecord(Record r) throws Exception {
    	updateRecord(r.getRid(), r.getUpadteDate(), r.getTreat(), r.getInfectDate(), r.getDrugHistory(), r.getMainComplaint(), r.getCurMedicalHistory());
    }
    
    /**
     * 新增申请单细节
     * @param data 参数数组，构造格式为{ApplyId, CheckId, State, CheckTime, Cond, CheckResult, Warning, Payment}
     * @see DatabaseFunc#insertCheckment(String, String, char, String, String, String, String, int)
     * @throws Exception
     */
    @Override
    public void insertCheckment(Object[] data) throws Exception {
    	String mySql = SqlFunc.SQL_INSERT_DETAIL_APPLY;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    } 
    
    /**
     * 新增申请单细节
     * @param applyId 申请单编号，长度15位的字符串，主键，非空，外键
     * @param cheId 检查项目编号，长度18位的字符串，主键，非空，外键
     * @param state 进行状态，一个数字，0未结账，1已结账未检查，2已检查，3已退费， 非空
     * @param checkTime 检查时间，格式为yyyy-mm-dd或yyyy.mm.dd
     * @param condition 文本
     * @param cheResult 文本
     * @param warning 文本
     * @param price 单项金额
     * @throws Exception
     */
    @Override
    public void insertCheckment(String applyId, String cheId, char state, String checkTime, String condition, 
			 					String cheResult, String warning, int price) throws Exception {
    	insertCheckment(new Object[] {applyId, cheId, state, checkTime, condition, cheResult, warning, price});   	
    }
    
    /**
     * 新增申请单细节
     * @param cf 检查单细节实例对象，构造格式详见CheckmentFeature类
     * @see Record#Record(String, String, char, String, String, String, String, String, String, String)
     * @throws Exception
     */
    @Override
    public void insertCheckment(String applyId, CheckFeature cf) throws Exception {
    	insertCheckment(new Object[] {applyId, cf.getCheId(), cf.getState(), cf.getCheckTime(), 
    								  cf.getCondition(), cf.getCheResult(), cf.getWarning(), cf.getPrice()});
    }

    /**
     * 新增申请单
     * @param data 参数数组，构造格式为{ApplyId, Eid, Pid}
     * @see DatabaseFunc#insertApply(String, String, String, CheckFeature[])
     * @throws Exception
     */
    @Override
    public void insertApply(Object[] data, CheckFeature[] features) throws Exception {
    	String mySql = SqlFunc.SQL_INSERT_APPLY;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        
        for(int i = 0; i < features.length; i++) {
        	insertCheckment(String.valueOf(data[0]), features[i]);
        }
    }

    /**
     * 新增申请单
     * @param applyId 申请单编号，长度15位的字符串，主键，非空，外键
     * @param Eid 医生身份证号，长度18位的字符串，主键，非空，外键
     * @param Pid 患者身份证号，长度18位的字符串，主键，非空，外键
     * @param features 申请单细节集合
     * @throws Exception
     */
    @Override
    public void insertApply(String applyId, String Eid, String Pid, CheckFeature[] features) throws Exception {
    	insertApply(new Object[] {applyId, Eid, Pid}, features);
    }
    
    /**
     * 新增申请单
     * @param apply 检查单实例对象，构造格式详见Checkment类
     * @see Checkment#Checkment(String, String, String, String[], String[])
     * @throws Exception
     */
    @Override
    public void insertApply(Checkment apply) throws Exception {
    	insertApply(new Object[] {apply.getApplyId(), apply.getPid(), apply.getEid()}, apply.getFeatures());
    }

    /**
     * 新增处方单单细节
     * @param data 参数数组，构造格式为{PrescribeId, MedId, State, Consum, Payment}
     * @see DatabaseFunc#insertRecord(String, String, char, int, int)
     * @throws Exception
     */
    @Override
    public void insertMedicine(Object[] data) throws Exception {
        String mySql = SqlFunc.SQL_INSERT_DETAIL_PRESCRIPTION;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    /**
     * 新增处方单细节
     * @param prescribeId 处方单编号，长度15位的字符串，主键，非空，外键
     * @param MedId 药物编号，长度18位的字符串，主键，非空，外键
     * @param State 进行状态，一个数字字符，0未结账，1已结账未检查，2已检查，3已退费， 非空
     * @param Consum 用量，int数字
     * @param Payment 单项金额，int数字
     * @throws Exception
     */
    @Override
    public void insertMedicine(String prescribeId, String MedId, char state, int consum, int price) throws Exception {
        insertCheckment(new Object[] {prescribeId, MedId, state, consum, price});
    }

    /**
     * 新增处方单细节
     * @param cf 检查单细节实例对象，构造格式详见PresFeature类
     * @see Prescription#Prescription(String, String, char, int, int)
     * @throws Exception
     */
    @Override
    public void insertMedicine(String prescribeId, PresFeature cf) throws Exception {
        insertMedicine(prescribeId, cf.getMedId(), cf.getState(), cf.getConsum(),cf.getPrice());
    }

    /**
     * 新增处方单
     * @param data 参数数组，构造格式为{prescribeId, Eid, Pid}
     * @see DatabaseFunc#insertRecord(String, String, String)
     * @throws Exception
     */
    @Override
    public void insertPrescription(Object[] data, PresFeature[] features) throws Exception {
        String mySql = SqlFunc.SQL_INSERT_PRESCRIPTION;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }

        for(int i = 0; i < features.length; i++) {
            insertMedicine(String.valueOf(data[0]), features[i]);
        }
    }

    /**
     * 新增处方单
     * @param PrescribeID 申请单编号，长度15位的字符串，主键，非空，外键
     * @param Eid 医生身份证号，长度18位的字符串，主键，非空，外键
     * @param Pid 患者身份证号，长度18位的字符串，主键，非空，外键
     * @param features 申请单细节集合
     * @throws Exception
     */
    @Override
    public void insertPrescription(String prescribeId, String Eid, String Pid, PresFeature[] features) throws Exception {
        insertPrescription(new Object[] {prescribeId, Eid, Pid}, features);
    }

    /**
     * 新增处方单
     * @param prescribeId 检查单实例对象，构造格式详见Prescription类
     * @see Prescription#Prescription(String, String, String, PresFeature[])
     * @throws Exception
     */
    @Override
    public void insertPrescription(Prescription prescription) throws Exception {
        insertPrescription(new Object[] {prescription.getPrescribeId(), prescription.getEid(), prescription.getPid()}, prescription.getFeatures());
    }

    /**
     * 获取病人病历
     * @param Pid 病人身份证号，长度为18位的字符串
     * @return Patient，病人实例对象，构造格式详见Patient类
     * @see Patient#Patient(String, String, String, int, String)
     * @throws Exception
     */
    @Override
    public List<Record> selectRecords(String Pid) throws Exception {
        List<Record> l = null;
        String sql = SqlFunc.SQL_SELECT_RECORDS;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {Pid});
        //Patient p = null;
        while(rs.next())
        {
            Record r;
            r = new Record(rs.getString("Rid"),
                    rs.getString("Pid"),
                    rs.getString("Eid"),
                    rs.getString("UpadteDate"),
                    rs.getString("Treat"),
                    rs.getString("DiagType"),
                    rs.getString("InfectDate"),
                    rs.getString("DrugHistory"),
                    rs.getString("MainComplaint"),
                    rs.getString("curMedicalHistory"));
            l.add(r);
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return l;
    }

    /**
     * 获取病人的单个病历
     * @param Pid 病人身份证号，长度为18位的字符串
     * @param Rid 病历号码，长度15位的字符串
     * @return Record，病历实例对象，构造格式详见Record类
     * @see Record#Record(String, String， String, String, String, String, String, String, String, String)
     * @throws Exception
     */
    @Override
    public Record selectRecord(String Pid, String Rid) throws Exception {
        Record r = null;
        String sql = SqlFunc.SQL_SELECT_RECORD;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {Pid, Rid});
        while(rs.next())
        {
            r = new Record(rs.getString("Rid"),
                    rs.getString("Pid"),
                    rs.getString("Eid"),
                    rs.getString("UpadteDate"),
                    rs.getString("Treat"),
                    rs.getString("DiagType"),
                    rs.getString("InfectDate"),
                    rs.getString("DrugHistory"),
                    rs.getString("MainComplaint"),
                    rs.getString("curMedicalHistory"));
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return r;
    }

    /**
     * 获取药物信息
     * @param MedId 药物编号，长度为15位的字符串
     * @return Medicine，病人实例对象，构造格式详见Medicine类
     * @see Medicine#Medicine(String, String, int, String, int)
     * @throws Exception
     */
    public Medicine selectMedicine(String MedId) throws Exception {
        Medicine medicine = null;
        String sql = SqlFunc.SQL_SELECT_MEDICINE;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {MedId});
        while(rs.next())
        {
            medicine = new Medicine(rs.getString("Rid"),
                    rs.getString("Pid"),
                    rs.getInt("Eid"),
                    rs.getString("Instruction"),
                    rs.getInt("UpadteDate"));
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return medicine;
    }

    /**
     * 获取多个药物信息
     * @param MedName 药物名称，长度为31位的变长字符串
     * @return Medicine，病人实例对象，构造格式详见Medicine类
     * @see Medicine#Medicine(String, String, int, String, int)
     * @throws Exception
     */
    public List<Medicine> selectMedicines(String MedName) throws Exception {
        List<Medicine> medicine = null;
        String sql = SqlFunc.SQL_SELECT_MEDICINES;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {MedName});
        while(rs.next())
        {
            Medicine m;
            m = new Medicine(rs.getString("Rid"),
                    rs.getString("Pid"),
                    rs.getInt("Eid"),
                    rs.getString("Instruction"),
                    rs.getInt("UpadteDate"));
            medicine.add(m);
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return medicine;
    }

    /**
     * 更改处方单状态
     * @param data 参数数组，构造格式为{Utime, onsetDate, treat, drugHistory, mainComplaint, curMedicalHistory, Rid}
     * @see DatabaseFunc#insertRecord(String, String, String, String, String, String, String)
     * @throws Exception
     */
    public void updateState(Object[] data) throws Exception {
        String mySql = SqlFunc.SQL_UPDATE_PRESCRIPTION;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.UPDATE, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void updatePrepare(String precrisbeId) throws Exception {
        updateState(new Object[] {"2", precrisbeId});
    }

    @Override
    public void updateDistribute(String precrisbeId) throws Exception {
        updateState(new Object[] {"3", precrisbeId});
    }

    @Override
    public void updateRepay(String precrisbeId) throws Exception {
        updateState(new Object[]{"5", precrisbeId});
    }

    @Override
    public Record findRecord(String Rid) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_RECORD;
        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {Rid});
        Record r = null;
        while(rs.next())
        {
            r = new Record(rs.getString("Rid"), rs.getString("Pid"), rs.getString("Eid"),
                    rs.getString("UpdateTime"), rs.getString("Treat"), rs.getString("DiagType"),
                    rs.getString("InfectTime"), rs.getString("DrugHistory"), rs.getString("MainComplaint"),
                    rs.getString("CurMediaHistory"));
        }

        return r;
    }

    @Override
    public List<Record> findHistoryRecords(String Pid) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_RECORDS;
        Connection conn = getConnection();

        return null;
    }

    /**
     * 获取病人
     * @param Pid 病人身份证号，长度为18位的字符串
     * @return Patient，病人实例对象，构造格式详见Patient类
     * @see Patient#Patient(String, String, String, int, String)
     * @throws Exception
     */
    @Override
    public Patient findPatient(String Pid) throws Exception {
        //预处理sql
        String sql = SqlFunc.SQL_SELECT_PATIENT;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {Pid});
        Patient p = null;
        while(rs.next())
        {
            p = new Patient(rs.getString("Pid"),
                    rs.getString("Password"),
                    rs.getString("Pname"),
                    rs.getInt("Page"),
                    rs.getString("Psex"));
            p.setPworktype(rs.getString("PWork"));
            p.setPtelphone(rs.getString("PPhone"));
            p.setPaddr(rs.getString("PAddr"));
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return p;
    }

    /**
     * 获取医生
     * @param Eid 医生身份证号，长度为18位的字符串
     * @return Doctor，医生实例对象，构造格式详见Doctor类
     * @see Doctor#Doctor(String, String, String, int, String, String)
     * @throws Exception
     */
    @Override
    public Doctor findDoctor(String Eid) throws Exception {
        //预处理sql
        String sql = SqlFunc.SQL_SELECT_DOCTOR;
        Connection conn = getConnection(); // 得到数据库连接
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {Eid});
        Doctor d = null;
        while(rs.next())
        {
            d = new Doctor(rs.getString("Eid"),
                    rs.getString("Password"),
                    rs.getString("Dname"),
                    rs.getInt("Dage"),
                    rs.getString("Dsex"),
                    rs.getString("RNo"));
            d.setTitle(rs.getString("Title"));
            d.setStartTime(rs.getString("StartTime"));
            d.setEndTime(rs.getString("EndTime"));
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return d;
    }

    /**
     * 查询科别信息
     * 可通过科别编号获取科别名，其反向操作，查询医生所属科别(名称)
     * @param data 查询所需信息，可为科别编号，科别名，医生身份证号
     * @param op 操作控制符，使用SqlOp枚举类
     * @see SqlOP
     * @return 取决于传入数据和操作符，可返回科别编号或科别名，错误返回null
     * @throws Exception
     */
    @Override
    public String findDepartment(String data, SqlOP op) throws Exception {
        String sql = null;
        switch (op)
        {
            case GETDEPNAME: sql = SqlFunc.SQL_SELECT_DEPARTMENT_NAME_BY_DEPID; break;
            case GETDEPNO: sql = SqlFunc.SQL_SELECT_DEPARTMENT_BY_NAME; break;
            case GETNAMEBYEID: sql = SqlFunc.SQL_SELECT_DEPARTMENT_BY_EID; break;
        }

        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, sql, SqlOP.SELECT, new Object[] {data});
        String Dep = null;
        while(rs.next())
        {
            switch (op)
            {
                case GETNAMEBYEID:
                case GETDEPNAME: Dep = rs.getString("DepName"); break;
                case GETDEPNO: Dep = rs.getString("DepNo"); break;
            }
        }

        return Dep;
    }

    /**
     * 获取预约单
     * @param pid 病人身份证号
     * @return 病人是科室预约：返回DepOrder对象；病人是专家预约：返回ProOrder对象；病人无预约：返回null
     * @throws Exception
     */
    @Override
    public Order findOrder(String pid) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_PREREGISTER_BY_PID;
        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {pid, pid});
        Order o = null;
        while(rs.next())
        {
            if(!rs.wasNull())
            {
                if(rs.getString(3).length() != 7)
                {
                    o = new ProOrder(rs.getLong("PRid"), rs.getString("Pid"), rs.getString("PTime"), rs.getString(3));
                }
                else
                {
                    o = new DepOrder(rs.getLong("PRid"), rs.getString("Pid"), rs.getString("PTime"), rs.getString(3));
                }
            }
        }

        return o;
    }

    @Override
    public String findDepRegister(String pid) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_DEP_REGISTER;
        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {pid});
        String DepNo = null;
        while(rs.next())
        {
            DepNo = rs.getString("DepNo");
        }

        return DepNo;
    }

    @Override
    public String findProRegister(String pid) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_PRO_REGISTER;
        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {pid});
        String Eid = null;
        while(rs.next())
        {
            Eid = rs.getString("Eid");
        }

        return Eid;
    }

    @Override
    public QueueNumber findQueueNumber(long qid) throws Exception {
        Connection conn = getConnection();
        String mySql = SqlFunc.SQL_SELECT_DEP_QUEUENUMBER;
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {qid});
        QueueNumber q = null;
        if(rs.next())
        {
            q = new QueueNumber(rs.getLong("Qid"), rs.getString("Pid"), rs.getString("EQTime"),
                        rs.getInt("PreFlag"), rs.getString("DepNo"), null);
        }
        else {
            mySql = SqlFunc.SQL_SELECT_PRO_QUEUENUMBER;
            rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {qid});
            while(rs.next())
            {
                q = new QueueNumber(rs.getLong("Qid"), rs.getString("Pid"), rs.getString("EQTime"),
                        rs.getInt("PreFlag"), null, rs.getString("Eid"));
            }
        }

        return q;
    }

    /**
     * 新增病人
     * @param pid 病人身份证号，长度为18位的字符串，非空
     * @param password 病人账号登录用密码，长度为6位的字符串，非空
     * @param pname 病人姓名，长度不超过31位，非空
     * @param page 病人年龄，非空
     * @param psex 病人性别，通常用‘男’或‘女’表示，非空
     * @param Pworktype 病人工作类型，长度不超过31位，可为null
     * @param Ptelphone 电话号码，长度为11位，可为null
     * @param Paddr 家庭住址，长度不超过63位，可为null
     * @throws Exception
     */
    @Override
    public void addPatient(String pid, String password, String pname, int page, String psex, String Pworktype, String Ptelphone, String Paddr) throws Exception {
        addPatient(new Object[] {pid, password, pname, page, psex, Pworktype, Ptelphone, Paddr});
    }

    /**
     * 新增病人
     * @param data 参数数组，构造格式为{pid, password, pname, page, psex, Pworktype, Ptelphone, Paddr}
     * @see DatabaseFunc#addPatient(String, String, String, int, String, String, String, String) 
     * @throws Exception
     */
    @Override
    public void addPatient(Object[] data) throws Exception {
        //预处理sql
        String mySql = SqlFunc.SQL_INSERT_PATIENT;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    /**
     * 新增病人
     * @param p 病人实例对象，构造格式详见Patient类
     * @see Patient#Patient(String, String, String, int, String) 
     * @throws Exception
     */
    @Override
    public void addPatient(Patient p) throws Exception {
        addPatient(p.getUid(), p.getPassword(), p.getName(), p.getAge(), p.getSex(), p.getPworktype(), p.getPtelphone(), p.getPaddr());
    }

    /**
     * 根据科别名查找专家
     * @param DepName 科别名称，以数据库中table_department的DepName项为准
     * @return List<Doctor>，医生实例对象列表，构造格式详见Doctor类
     * @see Doctor#Doctor(String, String, String, int, String, String)
     * @throws Exception
     */
    @Override
    public List<Doctor> searchProfessorByDepName(String DepName) throws Exception {
        String mySql = SqlFunc.SQL_SELECT_DEPARTMENT_BY_NAME;
        Connection conn = getConnection();
        ResultSet rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {DepName});
        String DepNo = null;
        while(rs.next())
        {
            DepNo = rs.getString("DepNo");
        }
        mySql = SqlFunc.SQL_SELECT_PROFESSOR;
        rs = executeSQL(conn, mySql, SqlOP.SELECT, new Object[] {DepNo});
        List<Doctor> dList = new ArrayList<Doctor>();
        while(rs.next())
        {
            Doctor d = new Doctor(rs.getString("Eid"),
                    rs.getString("Password"),
                    rs.getString("Dname"),
                    rs.getInt("Dage"),
                    rs.getString("Dsex"),
                    rs.getString("RNo"));
            d.setTitle(rs.getString("Title"));
            d.setStartTime(rs.getString("StartTime"));
            d.setEndTime(rs.getString("EndTime"));

            dList.add(d);
        }
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return dList;
    }

    @Override
    public void insertDepOrder(Object[] data) throws Exception {
        String mySql = SqlFunc.SQL_INSERT_DEP_PREREGISTER;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void insertDepOrder(long prid, String pid, String depNo, String ptime) throws Exception {
        insertDepOrder(new Object[] {prid, pid, depNo, ptime});
    }

    @Override
    public void insertDepOrder(DepOrder depOrder) throws Exception {
        insertDepOrder(depOrder.getPRid(), depOrder.getPid(), depOrder.getDepNo(), depOrder.getPTime());
    }

    @Override
    public void insertProOrder(Object[] data) throws Exception {
        String mySql = SqlFunc.SQL_INSERT_PRO_PREREGISTER;
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, data);
        try {
            DatabaseManager.closeAll(conn, null, null);
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void insertProOrder(long prid, String pid, String eid, String ptime) throws Exception {
        insertProOrder(new Object[] {prid, pid, eid, ptime});
    }

    @Override
    public void insertProOrder(ProOrder proOrder) throws Exception {
        insertProOrder(proOrder.getPRid(), proOrder.getPid(), proOrder.getEid(), proOrder.getPTime());
    }

    @Override
    public void insertLiveNum(long livenum, String pid, String data, SqlOP op) throws Exception {
        String mySql = null;
        switch (op)
        {
            case INSERT_LIVENUM_DEP: mySql = SqlFunc.SQL_INSERT_DEP_REGISTER; break;
            case INSERT_LIVENUM_PRO: mySql = SqlFunc.SQL_INSERT_PRO_REGISTER; break;
        }
        Connection conn = getConnection();
        executeSQL(conn, mySql, SqlOP.INSERT, new Object[] {livenum, pid, data});
    }

    @Override
    public void insertQueueNumber(QueueNumber q) throws Exception {
        String mySql = null;
        Connection conn = getConnection();
        if(q.isProQueue())
        {
            mySql = SqlFunc.SQL_INSERT_PRO_QUEUENUMBER;
            executeSQL(conn, mySql, SqlOP.INSERT, new Object[] {q.getQid(), q.getPid(), q.getEQTime(), q.getEid(), q.getPreFlag()});
        }
        else
        {
            mySql = SqlFunc.SQL_INSERT_DEP_QUEUENUMBER;
            executeSQL(conn, mySql, SqlOP.INSERT, new Object[] {q.getQid(), q.getPid(), q.getEQTime(), q.getDepNo(), q.getPreFlag()});
        }

    }


}
